<template>
  <div class="container">
    <section>
      <p id="loading">loading......</p>
    </section>
  </div>
</template>

<script>
export default {
  name: "Show3D",
  props: {
    msg: String,
  },
  data: function () {
    return {
    };
  },
  mounted: function () {
  },
};

let scene, camera, renderer, controls, guiControls, clock, mixer, mixer_left, mixer_right, mixer_back;
let cube;
let stats = initStats();
let texture, textureLoader, plane;
let play_left, play_center, play_right, play_back;

/* 场景 */
function initScene() {

    scene = new THREE.Scene();
    clock = new THREE.Clock();

    play_left = true;
    play_center = true;
    play_right = true;
    play_back = true;
}

/* 相机 */
function initCamera() {

    camera = new THREE.PerspectiveCamera(45, window.innerWidth / window.innerHeight, 0.1, 10000);
    camera.position.set(0, 0, 20);
    camera.lookAt(new THREE.Vector3(0, 0, 0));

}

/* 渲染器 */
function initRender() {

    renderer = new THREE.WebGLRenderer({antialias: true});
    renderer.setSize(window.innerWidth, window.innerHeight);
    renderer.setClearColor(0x0E3866);
    document.body.appendChild(renderer.domElement);

}

/* 灯光 */
function initLight() {

    scene.add(new THREE.AmbientLight(0xffffff));

    const pointLight = new THREE.PointLight( 0xffffff, 1, 1000 );
    pointLight.position.set( 500, 500, 500 );
    scene.add( pointLight );
}

/* 控制器 */
function initControls() {

    controls = new THREE.OrbitControls(camera, renderer.domElement);

    /* 属性参数默认 */

}

/* 调试插件 */
function initGui() {

    guiControls = new function () {

        this.left = function () {

            play_left = !play_left;
        };

        this.center = function () {

            play_center = !play_center;
        };

        this.right = function () {

            play_right = !play_right;
        };

        this.back = function () {

            play_back = !play_back;
        };
    };

    let gui = new dat.GUI({width: 150});

    gui.add(guiControls, 'left');
    gui.add(guiControls, 'center');
    gui.add(guiControls, 'right');
    gui.add(guiControls, 'back');

    return;
}

function loadTexture(path) {
    var texture = new THREE.Texture();
    var material = new THREE.MeshBasicMaterial({
        map: texture,
        overdraw: true,
        side: THREE.DoubleSide,
    });

    var image = new Image();
    image.onload = function () {
        texture.needsUpdate = true;
        material.map.image = this;

        render();
    };
    image.src = path;

    return material;
}

/* 场景中的内容 */
function initContent() {

    textureLoader = new THREE.TextureLoader();
    texture = textureLoader.load("./models/rabbit-pbr_out/rabbit-texture.png");
    texture.encoding = THREE.sRGBEncoding;
    texture.flipY = false;

    // 加载 glTF 格式的模型
    let loader = new THREE.GLTFLoader();/*实例化加载器*/
    /*
            loader.load('models/monkey_textured.glb', function(obj) {

                console.log(obj);

                obj.scene.position.x = 5;
                obj.scene.position.y = 5;
                obj.scene.position.z = 0;

                obj.scene.traverse(function (child) {
                    if (child.isMesh) {
                        let m = child;
                        m.receiveShadow = true;
                        m.castShadow = true;
                    }
                    if (child.isLight) {
                        let l = child;
                        l.castShadow = true;
                        l.shadow.bias = -.003;
                        l.shadow.mapSize.width = 2048;
                        l.shadow.mapSize.height = 2048;
                    }
                });

                scene.add(obj.scene);
            });
    */
    //loader.load('./models/rabbit-pbr_out/rabbit-pbr.gltf',function (obj) {
    loader.load('./models/rabbit-pbr_out/rabbit-pbr.gltf',function (obj) {

        console.log(obj);

        obj.scene.position.x = 0;
        obj.scene.position.y = 0;
        obj.scene.position.z = 0;

        //obj.scene.material.map = texture;

        document.getElementById('loading').style.display = 'none';

        obj.scene.traverse( function ( child ) {

            if ( child.isMesh ) {

                child.material = new THREE.MeshStandardMaterial({
                    map: texture,
                    color: 0xffffff,
                    skinning: true,
                    morphTargets: true,
                    morphNormals: true,
                });

                console.log(child.material);
            }
        } );

        mixer = new THREE.AnimationMixer( obj.scene );

        obj.animations.forEach( ( clip ) => {
            mixer.clipAction( clip ).play();
        } );

        scene.add(obj.scene);

    },function (xhr) {

        console.log( ( xhr.loaded / xhr.total * 100 ) + '% loaded' );

    },function (error) {

        console.log('load error!'+error.getWebGLErrorMessage());

    })

    loader.load('./models/rabbit-pbr_out/rabbit-pbr.gltf',function (obj) {

        console.log(obj);

        obj.scene.position.x = 2;
        obj.scene.position.y = 0;
        obj.scene.position.z = 2;

        obj.scene.rotation.y = -Math.PI/2;

        document.getElementById('loading').style.display = 'none';

        obj.scene.traverse( function ( child ) {

            if ( child.isMesh ) {

                child.material = new THREE.MeshStandardMaterial({
                    map: texture,
                    color: 0xff00ff,
                    skinning: true,
                    morphTargets: true,
                    morphNormals: true,
                });

                console.log(child.material);
            }
        } );

        mixer_right = new THREE.AnimationMixer( obj.scene );

        obj.animations.forEach( ( clip ) => {
            mixer_right.clipAction( clip ).play();
        } );

        scene.add(obj.scene);

    },function (xhr) {

        console.log( ( xhr.loaded / xhr.total * 100 ) + '% loaded' );

    },function (error) {

        console.log('load error!'+error.getWebGLErrorMessage());

    })

    loader.load('./models/rabbit-pbr_out/rabbit-pbr.gltf',function (obj) {

        console.log(obj);

        obj.scene.position.x = -2;
        obj.scene.position.y = 0;
        obj.scene.position.z = 2;

        obj.scene.rotation.y = Math.PI/2;

        document.getElementById('loading').style.display = 'none';

        obj.scene.traverse( function ( child ) {

            if ( child.isMesh ) {

                child.material = new THREE.MeshStandardMaterial({
                    map: texture,
                    color: 0xffff00,
                    skinning: true,
                    morphTargets: true,
                    morphNormals: true,
                });

                console.log(child.material);
            }
        } );

        mixer_left = new THREE.AnimationMixer( obj.scene );

        obj.animations.forEach( ( clip ) => {
            mixer_left.clipAction( clip ).play();
        } );

        scene.add(obj.scene);

    },function (xhr) {

        console.log( ( xhr.loaded / xhr.total * 100 ) + '% loaded' );

    },function (error) {

        console.log('load error!'+error.getWebGLErrorMessage());

    })

    loader.load('./models/rabbit-pbr_out/rabbit-pbr.gltf',function (obj) {

        console.log(obj);

        obj.scene.position.x = 0;
        obj.scene.position.y = 0;
        obj.scene.position.z = 4;

        obj.scene.rotation.y = Math.PI;

        document.getElementById('loading').style.display = 'none';

        obj.scene.traverse( function ( child ) {

            if ( child.isMesh ) {

                child.material = new THREE.MeshStandardMaterial({
                    map: texture,
                    color: 0x00ffff,
                    skinning: true,
                    morphTargets: true,
                    morphNormals: true,
                });

                console.log(child.material);
            }
        } );

        mixer_back = new THREE.AnimationMixer( obj.scene );

        obj.animations.forEach( ( clip ) => {
            mixer_back.clipAction( clip ).play();
        } );

        scene.add(obj.scene);

    },function (xhr) {

        console.log( ( xhr.loaded / xhr.total * 100 ) + '% loaded' );

    },function (error) {

        console.log('load error!'+error.getWebGLErrorMessage());

    })
    /*
            // import { BoxBufferGeometry } from 'three';
            // create a geometry
            const geometry = new THREE.BoxBufferGeometry(2, 2, 2);
            // create a default (white) Basic material
            const material = new THREE.MeshBasicMaterial();
            // create a Mesh containing the geometry and material
            cube = new THREE.Mesh(geometry, material);
            cube.position.y = -2;
            cube.position.x = -3;
            // add the mesh to the scene
            scene.add(cube);
    */
    /*
            var planematerial = new THREE.MeshLambertMaterial({ map : texture });
            plane = new THREE.Mesh(new THREE.PlaneGeometry(10, 10), planematerial);
            plane.doubleSided = true;
            plane.position.x = 0;
            plane.position.z = -20;
            plane.rotation.z = 0;  // Not sure what this number represents.
            scene.add(plane);
    */
    scene.background = new THREE.CubeTextureLoader()
        .setPath( 'images/' )
        .load( [
            'px.jpg',
            'nx.jpg',
            'py.jpg',
            'ny.jpg',
            'pz.jpg',
            'nz.jpg'
        ] );

    // var materials = [
    //   loadTexture("images/px.jpg"), // right
    //   loadTexture("images/nx.jpg"), // left
    //   loadTexture("images/py.jpg"), // top
    //   loadTexture("images/ny.jpg"), // bottom
    //   loadTexture("images/pz.jpg"), // back
    //   loadTexture("images/nz.jpg"), // front
    // ];

    // var cubmesh = new THREE.Mesh(
    //   new THREE.CubeGeometry(8, 8, 8, 1, 1, 1, materials),
    //   new THREE.MeshFaceMaterial({ side: THREE.DoubleSide })
    // );
    // cubmesh.scale.x = -1;
    // cubmesh.position.x = 3;
    // scene.add(cubmesh); //纹理贴图网格模型添加到场景中
}

/* 性能插件 */
function initStats() {

    let stats = new Stats();

    document.body.appendChild(stats.domElement);

    return stats;

}

/* 窗口变动触发 */
function onWindowResize() {

    camera.aspect = window.innerWidth / window.innerHeight;
    camera.updateProjectionMatrix();
    renderer.setSize(window.innerWidth, window.innerHeight);

}

/* 数据更新 */
function update() {

    stats.update();

}

/* 初始化 */
function init() {

    initScene();
    initCamera();
    initRender();
    initLight();
    initControls();
    initContent();
    initGui();

    /* 监听事件 */
    window.addEventListener('resize', onWindowResize, false);

}

/* 循环渲染 */
function animate() {

    requestAnimationFrame(animate);

    var delta = clock.getDelta();

    if ( mixer && play_center) mixer.update( delta );
    if ( mixer_left && play_left ) mixer_left.update( delta );
    if ( mixer_right && play_right ) mixer_right.update( delta );
    if ( mixer_back && play_back ) mixer_back.update( delta );

    renderer.render(scene, camera);

    update();
}

/* 初始加载 */
(function () {
    console.log("three init start...");

    init();
    animate();

    console.log("three init send...");
})();
</script>

